<template>
    <page-container>
        <FullPage>
            <j-card>
                <div class="box">
                    <div class="left">
                        <div class="left-content">
                            <TitleComponent data="基本信息" />
                            <j-alert
                                v-if="!!_error && modelRef?.id"
                                style="margin: 10px 0"
                                type="warning"
                            >
                                <template #message>
                                    <div
                                        style="
                                            display: flex;
                                            justify-content: space-between;
                                            align-items: center;
                                        "
                                    >
                                        <span
                                            style="
                                                width: calc(100% - 100px);
                                                text-align: center;
                                            "
                                            >{{ _error }}</span
                                        >
                                        <PermissionButton
                                            :popConfirm="{
                                                title: '确认启用',
                                                onConfirm: onActiveProduct,
                                            }"
                                            size="small"
                                            :hasPermission="'device/Product:action'"
                                        >
                                            立即启用
                                        </PermissionButton>
                                    </div>
                                </template>
                            </j-alert>
                            <j-form
                                :layout="'vertical'"
                                ref="formRef"
                                :model="modelRef"
                            >
                                <j-row :gutter="24">
                                    <j-col :span="24">
                                        <j-form-item
                                            label="名称"
                                            name="name"
                                            :rules="[
                                                {
                                                    required: true,
                                                    message: '请输入名称',
                                                },
                                                {
                                                    max: 64,
                                                    message: '最多输入64个字符',
                                                },
                                            ]"
                                        >
                                            <j-input
                                                placeholder="请输入名称"
                                                v-model:value="modelRef.name"
                                            />
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-form-item
                                            :name="['accessConfig', 'regionId']"
                                            :rules="[
                                                {
                                                    required: true,
                                                    message: '请选择服务地址',
                                                },
                                            ]"
                                        >
                                            <template #label>
                                                <span>
                                                    服务地址
                                                    <j-tooltip
                                                        title="阿里云内部给每台机器设置的唯一编号"
                                                    >
                                                        <AIcon
                                                            type="QuestionCircleOutlined"
                                                            style="
                                                                margin-left: 2px;
                                                            "
                                                        />
                                                    </j-tooltip>
                                                </span>
                                            </template>
                                            <j-select
                                                placeholder="请选择服务地址"
                                                v-model:value="
                                                    modelRef.accessConfig
                                                        .regionId
                                                "
                                                show-search
                                                @blur="productChange"
                                            >
                                                <j-select-option
                                                    v-for="item in regionsList"
                                                    :key="item.id"
                                                    :value="item.id"
                                                    :label="item.name"
                                                    >{{
                                                        item.name
                                                    }}</j-select-option
                                                >
                                            </j-select>
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-form-item
                                            :name="[
                                                'accessConfig',
                                                'instanceId',
                                            ]"
                                        >
                                            <template #label>
                                                <span>
                                                    实例ID
                                                    <j-tooltip
                                                        title="阿里云物联网平台中的实例ID,没有则不填"
                                                    >
                                                        <AIcon
                                                            type="QuestionCircleOutlined"
                                                            style="
                                                                margin-left: 2px;
                                                            "
                                                        />
                                                    </j-tooltip>
                                                </span>
                                            </template>
                                            <j-input
                                                placeholder="请输入实例ID"
                                                v-model:value="
                                                    modelRef.accessConfig
                                                        .instanceId
                                                "
                                                @blur="productChange"
                                            />
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-form-item
                                            :name="[
                                                'accessConfig',
                                                'accessKeyId',
                                            ]"
                                            :rules="[
                                                {
                                                    required: true,
                                                    message: '请输入accessKey',
                                                },
                                                {
                                                    max: 64,
                                                    message: '最多输入64个字符',
                                                },
                                            ]"
                                        >
                                            <template #label>
                                                <span>
                                                    accessKey
                                                    <j-tooltip
                                                        title="用于程序通知方式调用云服务API的用户标识"
                                                    >
                                                        <AIcon
                                                            type="QuestionCircleOutlined"
                                                            style="
                                                                margin-left: 2px;
                                                            "
                                                        />
                                                    </j-tooltip>
                                                </span>
                                            </template>
                                            <j-input
                                                placeholder="请输入accessKey"
                                                v-model:value="
                                                    modelRef.accessConfig
                                                        .accessKeyId
                                                "
                                                @blur="productChange"
                                            />
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-form-item
                                            :name="[
                                                'accessConfig',
                                                'accessSecret',
                                            ]"
                                            :rules="[
                                                {
                                                    required: true,
                                                    message:
                                                        '请输入accessSecret',
                                                },
                                                {
                                                    max: 64,
                                                    message: '最多输入64个字符',
                                                },
                                            ]"
                                        >
                                            <template #label>
                                                <span>
                                                    accessSecret
                                                    <j-tooltip
                                                        title="用于程序通知方式调用云服务费API的秘钥标识"
                                                    >
                                                        <AIcon
                                                            type="QuestionCircleOutlined"
                                                            style="
                                                                margin-left: 2px;
                                                            "
                                                        />
                                                    </j-tooltip>
                                                </span>
                                            </template>
                                            <j-input
                                                placeholder="请输入accessSecret"
                                                v-model:value="
                                                    modelRef.accessConfig
                                                        .accessSecret
                                                "
                                                @blur="productChange"
                                            />
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-form-item
                                            name="bridgeProductKey"
                                            :rules="{
                                                required: true,
                                                message: '请选择网桥产品',
                                            }"
                                        >
                                            <template #label>
                                                <span>
                                                    网桥产品
                                                    <j-tooltip
                                                        title="物联网平台对应的阿里云产品"
                                                    >
                                                        <AIcon
                                                            type="QuestionCircleOutlined"
                                                            style="
                                                                margin-left: 2px;
                                                            "
                                                        />
                                                    </j-tooltip>
                                                </span>
                                            </template>
                                            <j-select
                                                placeholder="请选择网桥产品"
                                                v-model:value="
                                                    modelRef.bridgeProductKey
                                                "
                                                show-search
                                            >
                                                <j-select-option
                                                    v-for="item in aliyunProductList"
                                                    :key="item.productKey"
                                                    :value="item.productKey"
                                                    :label="item.productName"
                                                    >{{
                                                        item.productName
                                                    }}</j-select-option
                                                >
                                            </j-select>
                                        </j-form-item>
                                    </j-col>
                                    <j-col :span="24">
                                        <p>产品映射</p>
                                        <j-collapse
                                            v-if="modelRef.mappings.length"
                                            :activeKey="activeKey"
                                            @change="onCollChange"
                                        >
                                            <j-collapse-panel
                                                v-for="(
                                                    item, index
                                                ) in modelRef.mappings"
                                                :key="index"
                                                :forceRender="false"
                                                :header="
                                                    item.productKey
                                                        ? aliyunProductList.find(
                                                              (i) =>
                                                                  i.productKey ===
                                                                  item.productKey,
                                                          )?.productName ||
                                                          `产品映射${index + 1}`
                                                        : `产品映射${index + 1}`
                                                "
                                            >
                                                <template #extra
                                                    ><AIcon
                                                        type="DeleteOutlined"
                                                        @click="delItem(index)"
                                                /></template>
                                                <j-row :gutter="24">
                                                    <j-col :span="12">
                                                        <j-form-item
                                                            label="阿里云产品"
                                                            :name="[
                                                                'mappings',
                                                                index,
                                                                'productKey',
                                                            ]"
                                                            :rules="{
                                                                required: true,
                                                                message:
                                                                    '请选择阿里云产品',
                                                            }"
                                                        >
                                                            <j-select
                                                                placeholder="请选择阿里云产品"
                                                                v-model:value="
                                                                    item.productKey
                                                                "
                                                                show-search
                                                            >
                                                                <j-select-option
                                                                    v-for="i in getAliyunProductList(
                                                                        item?.productKey ||
                                                                            '',
                                                                    )"
                                                                    :key="
                                                                        i.productKey
                                                                    "
                                                                    :value="
                                                                        i.productKey
                                                                    "
                                                                    :label="
                                                                        i.productName
                                                                    "
                                                                    >{{
                                                                        i.productName
                                                                    }}</j-select-option
                                                                >
                                                            </j-select>
                                                        </j-form-item>
                                                    </j-col>
                                                    <j-col :span="12">
                                                        <j-form-item
                                                            label="平台产品"
                                                            :name="[
                                                                'mappings',
                                                                index,
                                                                'productId',
                                                            ]"
                                                            :rules="[
                                                                {
                                                                    required: true,
                                                                    message:
                                                                        '请选择平台产品',
                                                                },
                                                                {
                                                                    validator:
                                                                        _validator,
                                                                    trigger:
                                                                        'change',
                                                                },
                                                            ]"
                                                        >
                                                            <!-- <j-select
                                                                placeholder="请选择平台产品"
                                                                v-model:value="
                                                                    item.productId
                                                                "
                                                                show-search
                                                            >
                                                                <j-select-option
                                                                    v-for="i in getPlatProduct(
                                                                        item.productId ||
                                                                            '',
                                                                    )"
                                                                    :key="i.id"
                                                                    :value="
                                                                        i?.id
                                                                    "
                                                                    :label="
                                                                        i.name
                                                                    "
                                                                    >{{
                                                                        i.name
                                                                    }}</j-select-option
                                                                >
                                                            </j-select> -->
                                                            <MSelect
                                                                v-model:value="
                                                                    item.productId
                                                                "
                                                                :options="
                                                                    getPlatProduct(
                                                                        item.productId ||
                                                                            '',
                                                                    )
                                                                "
                                                                @error="
                                                                    onPlatError
                                                                "
                                                            />
                                                        </j-form-item>
                                                    </j-col>
                                                </j-row>
                                            </j-collapse-panel>
                                        </j-collapse>
                                        <j-card v-else>
                                            <j-empty />
                                        </j-card>
                                    </j-col>
                                    <j-col :span="24">
                                        <j-button
                                            type="dashed"
                                            style="
                                                width: 100%;
                                                margin-top: 10px;
                                            "
                                            @click="addItem"
                                        >
                                            <AIcon
                                                type="PlusOutlined"
                                                style="margin-left: 2px"
                                            />添加
                                        </j-button>
                                    </j-col>
                                    <j-col :span="24" style="margin-top: 20px">
                                        <j-form-item
                                            label="说明"
                                            name="description"
                                            :rules="{
                                                max: 200,
                                                message: '最多输入200个字符',
                                            }"
                                        >
                                            <j-textarea
                                                v-model:value="
                                                    modelRef.description
                                                "
                                                placeholder="请输入说明"
                                                showCount
                                                :maxlength="200"
                                            />
                                        </j-form-item>
                                    </j-col>
                                </j-row>
                            </j-form>
                            <div v-if="type === 'edit'">
                                <PermissionButton
                                    type="primary"
                                    :loading="loading"
                                    @click="saveBtn"
                                    :hasPermission="[
                                        'Northbound/AliCloud:add',
                                        'Northbound/AliCloud:update',
                                    ]"
                                >
                                    保存
                                </PermissionButton>
                            </div>
                        </div>
                    </div>
                    <div class="right">
                        <Doc />
                    </div>
                </div>
            </j-card>
        </FullPage>
    </page-container>
</template>

<script lang="ts" setup>
import Doc from './doc.vue';
import {
    savePatch,
    detail,
    getRegionsList,
    getAliyunProductsList,
    queryProductList,
} from '@/api/northbound/alicloud';
import _ from 'lodash-es';
import { onlyMessage } from '@/utils/comm';
import MSelect from '../../components/MSelect/index.vue';
import { _deploy } from '@/api/device/product';

const router = useRouter();
const route = useRoute();

const formRef = ref();
const _errorSet = ref<Set<string>>(new Set());

const modelRef = reactive({
    id: undefined,
    name: undefined,
    accessConfig: {
        regionId: undefined,
        instanceId: undefined,
        accessKeyId: undefined,
        accessSecret: undefined,
    },
    bridgeProductKey: undefined,
    bridgeProductName: undefined,
    mappings: [
        {
            productKey: undefined,
            productId: undefined,
        },
    ],
    description: undefined,
});

const addItem = () => {
    activeKey.value.push(String(modelRef.mappings.length));
    modelRef.mappings.push({
        productKey: undefined,
        productId: undefined,
    });
};

const delItem = (index: number) => {
    modelRef.mappings.splice(index, 1);
};

const productList = ref<Record<string, any>[]>([]);
const regionsList = ref<Record<string, any>[]>([]);
const aliyunProductList = ref<Record<string, any>[]>([]);
const loading = ref<boolean>(false);
const type = ref<'edit' | 'view'>('edit');
const activeKey = ref<string[]>(['0']);

const queryRegionsList = async () => {
    const resp = await getRegionsList();
    if (resp.status === 200) {
        regionsList.value = resp.result as Record<string, any>[];
    }
};
const getProduct = async () => {
    const resp = await queryProductList({
        paging: false,
        sorts: [{ name: 'createTime', order: 'desc' }],
    });
    if (resp.status === 200) {
        productList.value = resp?.result as Record<string, any>[];
    }
};

const getAliyunProduct = async (data: any) => {
    if (data.regionId && data.accessKeyId && data.accessSecret) {
        const resp: any = await getAliyunProductsList(data);
        if (resp.status === 200) {
            aliyunProductList.value = resp?.result?.data as Record<
                string,
                any
            >[];
        }
    }
};

const productChange = () => {
    const data = modelRef.accessConfig;
    getAliyunProduct(data);
};

const getPlatProduct = (val: string) => {
    const arr = modelRef.mappings.map((item) => item?.productId) || [];
    const checked = _.cloneDeep(arr);
    const _index = checked.findIndex((i) => i === val);
    checked.splice(_index, 1);
    const list = productList.value.filter(
        (i: any) => !checked.includes(i?.id as any),
    );
    return list || [];
};

const getAliyunProductList = (val: string) => {
    const items = modelRef.mappings.map((item) => item?.productKey) || [];
    const checked = _.cloneDeep(items);
    const _index = checked.findIndex((i) => i === val);
    checked.splice(_index, 1);
    const list = aliyunProductList.value?.filter(
        (i: any) => !checked.includes(i?.productKey as any),
    );
    return list || [];
};

const onCollChange = (_key: string[]) => {
    activeKey.value = _key;
};

const _error = computed(() => {
    return _errorSet.value.size ? `当前选择的部分产品为禁用状态` : ''
})

const onActiveProduct = async () => {
    [..._errorSet.value.values()].forEach(async (i: any) => {
        const resp = await _deploy(i).catch((error) => {
            onlyMessage('操作失败', 'error');
        });
        if(resp?.status === 200) {
            _errorSet.value.delete(i)
            onlyMessage('操作成功！');
        }
    });
    await getProduct();
};

const onPlatError = (val: any) => {
    const _item = productList.value.find((item) => item.id === val);
    if (val && _item && !_item?.state) {
        _errorSet.value.add(val)
    }
};

const _validator = (_rule: any, value: string): Promise<any> =>
    new Promise((resolve, reject) => {
        const _item = productList.value.find((item) => item.id === value);
        if(!modelRef.id || modelRef.id === ':id') {
            return resolve('');
        } else if (!_item && value) {
            return reject('关联产品已被删除，请重新选择');
        }
        return resolve('');
    });

const saveBtn = () => {
    formRef.value
        .validate()
        .then(async (data: any) => {
            const product = (aliyunProductList.value || []).find(
                (item: any) => item?.productKey === data?.bridgeProductKey,
            );
            data.bridgeProductName = product?.productName || '';
            loading.value = true;
            const resp = await savePatch({
                ...toRaw(modelRef),
                ...data,
            }).finally(() => {
                loading.value = false;
            });
            if (resp.status === 200) {
                onlyMessage('操作成功！');
                formRef.value.resetFields();
                router.push('/iot/northbound/AliCloud');
            }
        })
        .catch((err: any) => {
            const _arr = err.errorFields.map((i: any) => i.name);
            _arr.map((item: string | any[]) => {
                if (item.length === 3 && !activeKey.value.includes(item[1])) {
                    activeKey.value.push(item[1]);
                }
            });
        });
};
watch(
    () => route.params?.id,
    async (newId) => {
        if (newId) {
            queryRegionsList();
            await getProduct();
            if (newId === ':id' || !newId) return;
            const resp = await detail(newId as string);
            const _data: any = resp.result;
            if (_data) {
                getAliyunProduct(_data?.accessConfig);
            }
            Object.assign(modelRef, _data);
            activeKey.value = (_data?.mappings || []).map(
                (_: any, index: number) => index,
            );
        }
    },
    { immediate: true, deep: true },
);

watch(
    () => route.query.type,
    (newVal) => {
        if (newVal) {
            type.value = newVal as 'edit' | 'view';
        }
    },
    { immediate: true, deep: true },
);
</script>

<style scoped lang="less">
.box {
    position: relative;
    .left {
        .left-content {
            width: 66%;
        }
    }
    .right {
        width: 33%;
        position: absolute;
        right: 0;
        top: 0;
        overflow-y: auto;
        height: 100%;
    }
}
</style>